package loader
{
	import flash.utils.ByteArray;
	
	import mx.messaging.AbstractConsumer;

	public class AbstractLoader
	{
		internal var progressFunc:Function;
		internal var completedFunc:Function;
		internal var errorFunc:Function;

		internal var lastLoadTime:int = 0;
		internal var lastLoadedBytes:int = 0;
		
		internal var desc:String;
		
		public function AbstractLoader():void
		{
		}
		
		public function startLoad( url:String, desc:String, onProgress:Function, onCompleted:Function, onErrorFunc:Function = null ):void
		{
			this.desc = desc;
			this.progressFunc = onProgress;
			this.completedFunc = onCompleted;
			this.errorFunc = onErrorFunc;
			
			this.lastLoadedBytes = 0;
			
			this.lastLoadTime = int( new Date().getTime() );
		}
		
		public function onProgress( loadedBytes:int, totalBytes:int ):void
		{
			if( progressFunc  is Function  )
			{
				var curLoadedBytes:int = loadedBytes - lastLoadedBytes;
				
				var curTime:int = int( ( new Date() ).getTime() / 1000 );
				
				var loadedTime:int = curTime - lastLoadTime;
				
				if( loadedTime == 0 )
				{
					loadedTime = 1;
				}
				
				// kb/s
				var speed:Number = Math.floor( curLoadedBytes * 10 / 1024 / loadedTime ) / 10;
				
				var percent:Number = Math.floor( loadedBytes / totalBytes );
				
				lastLoadTime = curTime;
				
				lastLoadedBytes = loadedBytes;
				
				progressFunc( desc, loadedBytes, totalBytes, speed, percent  );
			}
			
		}
		
		public function onCompleted():void
		{	
			if( completedFunc is Function )
			{
				completedFunc( this );
			}
		}
		
		public function onError( errorData:Object ):void
		{
			if( errorFunc is Function )
			{
				errorFunc( errorData );
			}
		}
		
		
		public function get content():Object
		{
			throw new Error( "this is a abstract method, need to be implemented !" );
		}
		
	}
}